package org.zjt.agent;

import net.bytebuddy.ByteBuddy;
import net.bytebuddy.dynamic.ClassFileLocator;
import net.bytebuddy.implementation.FixedValue;
import net.bytebuddy.matcher.ElementMatchers;
import net.bytebuddy.pool.TypePool;
import org.zjt.agent.domain.Person;
import org.zjt.agent.domain.Role;

import java.util.concurrent.*;
import java.util.concurrent.atomic.AtomicInteger;

/**
 * 我的Java代理
 *
 * @author   单红宇(365384722)
 * @myblog  http://blog.csdn.net/catoop/
 * @create    2016年3月30日
 *
 *  ide启动： -javaagent:G:\java-agent-demo-1.0-SNAPSHOT.jar=2222
 *
 *            -javaagent:G:\java-agent-demo-0.0.1-SNAPSHOT.jar=org.zjt.agent.domain -verbose:class
 *
 *   命令行： java -javaagent:G:\myagent.jar=Hello1 -javaagent:G:\myagent.jar=agent参数 -jar myapp.jar
 *
 *   -Xbootclasspath/p:F:\java-agent-demo-0.0.1-SNAPSHOT.jar  -javaagent:F:\java-agent-demo-0.0.1-SNAPSHOT.jar
 *
 *
 *
 *   -Xbootclasspath/p:F:\transmittable-thread-local-2.3.0-SNAPSHOT.jar -javaagent:F:\transmittable-thread-local-2.3.0-SNAPSHOT.jar -DgenerateClass=true -DgenerateClassPath="F:\Idea workspace\transmittable-thread-local\src\main\java\com\alibaba\ttl\threadpool\agent\transformer"
 *
 *
 *  -Xbootclasspath/p:F:\transmittable-thread-local-2.3.0-SNAPSHOT.jar -javaagent:F:\transmittable-thread-local-2.3.0-SNAPSHOT.jar
 */


public class MyApp {

    private static final ThreadLocal<Integer> THREAD_LOCAL = ThreadLocal.withInitial(() -> 0);

    public static void main(String[] args) {
        Person person = new Person();

        System.err.println(person.toString());

        test2();
    }


    public static void modifyClass() {

        TypePool typePool = TypePool.Default.ofClassPath();
        new ByteBuddy()
                .redefine(typePool.describe("org.zjt.agent.domain.Person").resolve(), ClassFileLocator.ForClassLoader.ofClassPath())
                .defineField("qux", String.class)
                .method(ElementMatchers.named("toString"))
                .intercept(FixedValue.value("Hello World!"))
                .make()
                .load(ClassLoader.getSystemClassLoader());

        Person person = new Person();

        System.err.println(person.toString());
    }




    public static void test2() {
        ExecutorService executorService = Executors.newFixedThreadPool(2);
        executorService.submit(()->System.out.println(Thread.currentThread().getName() +"-------is running-------"));

        new Thread(()->THREAD_LOCAL.set(22)).start();

        for (int i = 0; i < 4; i++) {
            executorService.submit(()->THREAD_LOCAL.set(THREAD_LOCAL.get() + 1));
        }

        for (int i = 0; i < 4; i++) {
            executorService.submit(()->System.out.println(THREAD_LOCAL.get()));
        }



        Person person = new Person();
        person.setAddr("ssssss");

        executorService.shutdown();
    }


    public static void ThreadPoolExecutorTest() {
        AtomicInteger count = new AtomicInteger(0);

        ThreadPoolExecutor threadPoolExecutor =
                new ThreadPoolExecutor(1, 1, 60, TimeUnit.SECONDS, new ArrayBlockingQueue<>(1),
                r -> {
                    Thread thread = new Thread();
                    thread.setName("ZHANG-"+count.getAndIncrement());
                    return thread;
                }
                , (r, executor) -> {
                    System.err.println(r +" " + executor);
                    throw new RuntimeException("-----------------------");
                });

        for (int i = 0; i < 10; i++) {
            threadPoolExecutor.submit(() -> {
                try {
                    Thread.sleep(2 * 1000);
                } catch (InterruptedException e) {
                    e.printStackTrace();
                }
            });
        }




        threadPoolExecutor.shutdown();
    }


    public static void test1()throws InterruptedException  {
        Person person = new Person();
        Role role = new Role();
        System.err.printf("person.class:%s\tclassload:%s\n",person.getClass(),person.getClass().getClassLoader());
        System.err.printf("role.class:%s\tclassload:%s\n",role.getClass(),role.getClass().getClassLoader());

        role.setId(1);
        role.setName("admin");

        person.setRoleId(1);
        person.setName("zhangsan");
        person.setAddr("xi,an");
        person.setId(2);
        person.setAge(25);

        System.out.println(role.toString());
        System.out.println(person.toString());



        Person person2 = new Person();
        person2.setRoleId(1);
        person2.setName("zhangsan");
        Thread.sleep(20000);


        System.out.println("hello --------word");
    }
}